package admission.ecnu.service;

import java.util.ArrayList;
import java.util.Collection;
import java.util.HashMap;
import java.util.Iterator;
import java.util.List;
import java.util.Set;

import org.json.JSONObject;

import admission.ecnu.dao.classInfoDao;
import admission.ecnu.dao.teacherInfoDao;
import admission.ecnu.interfaces.IRnsService;
import admission.ecnu.mainservlet.RnsContext;
import admission.ecnu.object.DataManager;
import admission.ecnu.object.OClassInfo;
import admission.ecnu.object.OResult;
import admission.ecnu.object.OTeacherInfo;

import com.ecnu.sei.app.Scheduler;
import com.ecnu.sei.app.course.AbstractCourse;
import com.ecnu.sei.app.course.CourseInfo;
import com.ecnu.sei.app.course.ExamInfo;
import com.ecnu.sei.app.course.PublicCompulsory;
import com.ecnu.sei.app.course.SpecialtyCompulsory;
import com.ecnu.sei.app.course.SpecialtyElective;
import com.ecnu.sei.app.resources.Classroom;
import com.ecnu.sei.app.teacher.AbstractTeacher;
import com.ecnu.sei.app.teacher.Administrator;
import com.ecnu.sei.app.teacher.AssociateProfessor;
import com.ecnu.sei.app.teacher.ForeignTeacher;
import com.ecnu.sei.app.teacher.Lecturer;
import com.ecnu.sei.app.teacher.Official;
import com.ecnu.sei.app.teacher.Professor;
import com.ecnu.sei.app.util.Utils;

public class getExamArrangement implements IRnsService {

  private static HashMap<String, AbstractTeacher> tIdToITeacherMap = new HashMap<String, AbstractTeacher>();

  @Override
  public void executeService(RnsContext context) throws Exception {
    // TODO Auto-generated method stub
    JSONObject obj = context.getJsonRequestObject();
    System.out.print(obj.toString());
    if (!DataManager.USER_ID.equals(obj.get("key"))) {
      JSONObject jsonReturn = new JSONObject();
      jsonReturn.put("returnCode", DataManager.RETURN_WRONGKEY);
      context.setJsonResponseObject(jsonReturn);
      return;
    }

    // System.out.println("Loading data...");
    // loadData();
    // System.out.println("Generating schedule...");
    // Scheduler.getScheduler().generateSchedule();
    // System.out.println("Saving data...");
    // saveData();

    JSONObject jsonReturn = new JSONObject();
    JSONObject jsonReturnValue = new JSONObject();

    jsonReturnValue.put("date", "2012-12-1 12:12:12");
    jsonReturnValue.put("grade", "0903");
    jsonReturnValue.put("time", "8:00-10:00");
    jsonReturnValue.put("courseName", "shuxue");
    jsonReturnValue.put("studentNum", "60");
    jsonReturnValue.put("examRoom", "xin 4");
    jsonReturnValue.put("class", "class 1");
    jsonReturnValue.put("teacher", "ZhangJunyang");
    jsonReturnValue.put("examMainTeacher", "ZhangJunyang");
    jsonReturnValue.put("invigilator1", "Baoyu");
    jsonReturnValue.put("invigilator2", "ChenHui");
    jsonReturnValue.put("inspectors", "He");
    jsonReturnValue.put("backup", "He2");

    jsonReturn.put("returnCode", DataManager.RETURN_SUCCESSFUL);
    jsonReturn.put("returnValue", jsonReturnValue);

    context.setJsonResponseObject(jsonReturn);

    // ArrayListJsonResponseObject(json);
  }

  private static void loadClassInfo() {
    ArrayList<OClassInfo> classDBObjList = (ArrayList<OClassInfo>) new classInfoDao()
        .classSelect();

    for (OClassInfo classObj : classDBObjList) {
      CourseInfo courseInfo = new CourseInfo(classObj.getClassId(),
          classObj.getGrade(), classObj.getCurriculum(),
          tIdToITeacherMap.get(classObj.getTeacher()), Integer.valueOf(classObj
              .getClassTime().split("_")[0]) - 1,// dayOfWeek
          Utils.getDayHourFromStartTime(Integer.valueOf(classObj.getClassTime()
              .split("_")[1])), // dayHour
          Integer.valueOf(classObj.getStudentNum()), new Classroom(
              classObj.getClassroom(), Integer.MAX_VALUE));

      Scheduler scheduler = Scheduler.getScheduler();
      if (classObj.getType().equals("PC")) {
        scheduler.addCourse(new PublicCompulsory(courseInfo));
      } else if (classObj.getType().equals("SC")) {
        scheduler.addCourse(new SpecialtyCompulsory(courseInfo));
      } else if (classObj.getType().equals("SE")) {
        scheduler.addCourse(new SpecialtyElective(courseInfo));
      }
    }
  }

  private static void loadTeacherInfo() {
    ArrayList<OTeacherInfo> teacherDBObjList = (ArrayList<OTeacherInfo>) new teacherInfoDao()
        .teacherSelect();
    for (OTeacherInfo teacherObj : teacherDBObjList) {
      AbstractTeacher teacher = null;
      String teacherId = teacherObj.getTeacherId();
      String teacherName = teacherObj.getName();
      if (teacherObj.getTitle().equals("AP")) {
        teacher = new AssociateProfessor(teacherId, teacherName);
      } else if (teacherObj.getTitle().equals("FT")) {
        teacher = new ForeignTeacher(teacherId, teacherName);
      } else if (teacherObj.getTitle().equals("AD")) {
        teacher = new Administrator(teacherId, teacherName);
      } else if (teacherObj.getTitle().equals("Lecturer")) {
        teacher = new Lecturer(teacherId, teacherName);
      } else if (teacherObj.getTitle().equals("Official")) {
        teacher = new Official(teacherId, teacherName);
      } else if (teacherObj.getTitle().equals("Professor")) {
        teacher = new Professor(teacherId, teacherName);
      }
      tIdToITeacherMap.put(teacherId, teacher);
      Scheduler.getScheduler().addTeacher(teacher);

    }
  }

  public List<OResult> getExamSchedule() {
    List<OResult> results = new ArrayList<OResult>();
    Collection<Set<AbstractCourse>> all = Scheduler.getScheduler()
        .getExamSchedule().values();
    for (Iterator<Set<AbstractCourse>> iterator = all.iterator(); iterator
        .hasNext();) {
      Set<AbstractCourse> courseSet = iterator.next();
      for (AbstractCourse course : courseSet) {
        results.add(getResult(course));
      }
    }
    return results;
  }

  private OResult getResult(AbstractCourse course) {
    CourseInfo info = course.getCourseInfo();
    ExamInfo examInfo = info.getExamInfo();
    AbstractTeacher chief = examInfo.getChief();
    AbstractTeacher[] vices = examInfo.getVices();
    OResult result = new OResult();
    result.setCourse_id(info.getCourseId());
    result.setCourse_name(info.getCourseName());
    result.setTest_time(examInfo.getTime().toString());
    result.setChief_teacher(chief.getName());

    result.setVice_teacher01(vices[0].getName());
    if (2 == vices.length) {
      result.setVice_teacher02(vices[1].getName());
    }

    result.setPatrol_teacher(examInfo.getPatrol().getName());
    result.setBackup_teacher(examInfo.getBackup().getName());

    return result;
  }
}